package cn.cdutetc.foxwatch.serveice.imp;

import cn.cdutetc.foxwatch.common.ExceptionEnum;
import cn.cdutetc.foxwatch.config.JedisConnectionFactory;
import cn.cdutetc.foxwatch.exception.MyException;
import cn.cdutetc.foxwatch.mapper.UserInfoMapper;
import cn.cdutetc.foxwatch.pojo.PagePojo;
import cn.cdutetc.foxwatch.pojo.UserInfo;
import cn.cdutetc.foxwatch.pojo.tripartite.PhonePojo;
import cn.cdutetc.foxwatch.serveice.UserInfoService;
import cn.cdutetc.foxwatch.utils.JwtUtil;
import cn.cdutetc.foxwatch.utils.Md5Util;
import cn.hutool.core.util.RandomUtil;
import cn.hutool.http.HttpUtil;
import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import io.micrometer.common.util.StringUtils;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.util.ObjectUtils;
import redis.clients.jedis.Jedis;

import java.time.LocalDate;
import java.util.HashMap;
import java.util.Map;

@Service
public class UserInfoServiceImpl extends ServiceImpl<UserInfoMapper, UserInfo> implements UserInfoService {

    @Value("${baseUrl.phoneBackUrl}")
    private String phoneUrl;

    @Override
    public PagePojo<UserInfo> queryUserInfoPage(UserInfo userInfo) {

        return null;
    }

    @Override
    public Boolean register(UserInfo userPojo) throws MyException {
        String username = userPojo.getUserName();
        String password = userPojo.getPassword();
        String rePassword = userPojo.getRePassword();
        //参数校验

        if (StringUtils.isEmpty(password) || StringUtils.isEmpty(rePassword) || StringUtils.isEmpty(username)) {
            throw new MyException(200, ExceptionEnum.ParameterError.getDesc());
        }
        //密码校验
        if (!password.equals(rePassword)) {
            throw new MyException(200, ExceptionEnum.PasswordRepeat.getDesc());
        }
        //查询用户是否存在
        LambdaQueryWrapper<UserInfo> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(UserInfo::getUserName, username);
        UserInfo user = this.baseMapper.selectOne(queryWrapper);
        //用户已存在
        if (user != null) {
            throw new MyException(200, ExceptionEnum.UserExist.getDesc());
        }
        //明文转密文
        String mdPsd = Md5Util.getMD5String(password);
        userPojo.setPassword(mdPsd);
        int i = this.baseMapper.insert(userPojo);
        return i == 1;
    }

    @Override
    public String login(UserInfo userPojo) throws MyException {
        String username = userPojo.getUserName();
        String password = userPojo.getPassword();

        //参数校验
        if (StringUtils.isEmpty(password) || StringUtils.isEmpty(username)) {
            throw new MyException(200, ExceptionEnum.ParameterError.getDesc());
        }
        //查询用户是否存在
        LambdaQueryWrapper<UserInfo> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(UserInfo::getUserName, username);

        UserInfo user = this.baseMapper.selectOne(queryWrapper);
        //用户不存在
        if (user == null) {
            throw new MyException(200, ExceptionEnum.UserNotExist.getDesc());
        }
        //密码校验
        String mdPsd = Md5Util.getMD5String(password);
        if (!mdPsd.equals(user.getPassword())) {
            throw new MyException(200, ExceptionEnum.PasswordError.getDesc());
        }
        //登录成功
        Map<String, Object> map = new HashMap<>();
        map.put("userId", user.getId());
        map.put("userName", user.getUserName());
        return JwtUtil.genToken(map);
    }

    @Override
    public String emailLogin(UserInfo user, String code) throws MyException {
        Jedis jedis = JedisConnectionFactory.getJedis();
        try {
            String email = user.getEmail();
            if (StringUtils.isEmpty(code) || StringUtils.isEmpty(email)) {
                throw new MyException(200, ExceptionEnum.ParameterError.getDesc());
            }
            String codeValue = jedis.hget(email, "code");
            System.out.println("codeValue:" + codeValue);
            if (StringUtils.isEmpty(codeValue)) {
                throw new MyException(200, ExceptionEnum.EmailCodeError.getDesc());
            }
            if (codeValue.equals(code)) {
                LambdaQueryWrapper<UserInfo> queryWrapper = new LambdaQueryWrapper<>();
                queryWrapper.eq(UserInfo::getEmail, email);
                UserInfo selectUser = this.baseMapper.selectOne(queryWrapper);
                if (selectUser == null) {
                    //  注册用户
                    UserInfo registeredUser = this.registerUser(user);
                    return getToken(registeredUser);
                } else {
                    System.out.println("用户已存在,直接登录");
                    return getToken(selectUser);
                }
            } else {
                throw new MyException(200, ExceptionEnum.CodeError.getDesc());
            }

        } finally {
            if (jedis != null) {
                jedis.close();
            }
        }
    }

    @Override
    public String phoneLogin(PhonePojo phone) throws MyException {
        String access_token = phone.getAccess_token();
        String open_id = phone.getOpenid();
        System.out.println(access_token + "," + open_id);
        String res = HttpUtil.post(phoneUrl, JSON.toJSONString(phone));
        JSONObject jsonObject = JSON.parseObject(res);
        Boolean success = jsonObject.getBoolean("success");
        if (success) {
            String phoneNum = jsonObject.getString("phoneNum");
            UserInfo searchUser = this.searchUser("phone", phoneNum);
            //用户不存在
            if (ObjectUtils.isEmpty(searchUser)) {
                UserInfo registeredUser = this.registerUser(UserInfo.builder().phone(phoneNum).build());
                return getToken(registeredUser);
            } else {
                return getToken(searchUser);
            }
        } else {
            throw new MyException(200, ExceptionEnum.PhoneCodeError.getDesc());
        }
    }

    @Override
    public String weixinLogin(UserInfo user, String code) throws MyException {
//          暂未接通需要审核
//        System.out.println("code:" + code);
//        String AppId = AppInfo.APP_INFO.getAPP_ID();
//        String AppSecret = AppInfo.APP_INFO.getAPP_SECRET();
//        String url = "https://api.weixin.qq.com/sns/jscode2session?appid=" + AppId + "&secret=" + AppSecret + "&js_code=" + code + "&grant_type=authorization_code";
//        System.out.println(url);
//        String result = HttpUtil.get(url);
//        return Result.success(result);
        String openid = user.getOpenid();
        UserInfo searchUser = this.searchUser("openid", openid);
        //用户不存在
        if (ObjectUtils.isEmpty(searchUser)) {
            UserInfo registeredUser = this.registerUser(UserInfo.builder().openid(openid)
                    .avatarUrl(user.getAvatarUrl()).build());
            return getToken(registeredUser);
        } else {
            return getToken(searchUser);
        }
    }

    public String getToken(UserInfo user) {
        HashMap<String, Object> map = new HashMap<>();
        map.put("userId", user.getId());
        map.put("userName", user.getUserName());
        map.put("nickName", user.getNickName());
        return JwtUtil.genToken(map);
    }

    public UserInfo registerUser(UserInfo user) {
        String nickName = RandomUtil.randomString(10);
        user.setNickName(nickName);
        user.setCreateTime(LocalDate.now());
        user.setUpdateTime(LocalDate.now());
        this.baseMapper.insert(user);
        return user;
    }

    public UserInfo searchUser(String key, Object value) {
        QueryWrapper<UserInfo> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq(key, value);
        return this.baseMapper.selectOne(queryWrapper);
    }

}
